package com.kakarote.admin.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollectionUtil;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.kakarote.core.common.enums.AdminRoleTypeEnum;
import com.kakarote.admin.entity.PO.AdminConfig;
import com.kakarote.admin.entity.PO.AdminMenu;
import com.kakarote.admin.entity.PO.AdminUser;
import com.kakarote.admin.entity.VO.AdminMenuVO;
import com.kakarote.admin.mapper.AdminMenuMapper;
import com.kakarote.admin.service.IAdminConfigService;
import com.kakarote.admin.service.IAdminMenuService;
import com.kakarote.admin.service.IAdminUserService;
import com.kakarote.core.servlet.ApplicationContextHolder;
import com.kakarote.core.servlet.BaseServiceImpl;
import com.kakarote.core.utils.RecursionUtil;
import com.kakarote.core.utils.UserUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * <p>
 * 后台菜单表 服务实现类
 * </p>
 *
 * @author zhangzhiwei
 * @since 2020-04-27
 */
@Service
public class AdminMenuServiceImpl extends BaseServiceImpl<AdminMenuMapper, AdminMenu> implements IAdminMenuService {

    @Autowired
    private IAdminUserService adminUserService;

    /**
     * 查询用户所拥有的菜单权限
     *
     * @param userId 用户列表
     * @return 菜单权限的并集
     */
    @Override
    public List<AdminMenu> queryMenuList(Long userId) {
        //超管用户拥有全部权限
        if (UserUtil.isAdmin()) {
            return query().list();
        }


        AdminUser adminUser = adminUserService.getById(userId);
        return getBaseMapper().queryMenuList(userId, adminUser.getDeptId());

    }

    /**
     * 查询用户所拥有的项目菜单权限
     *
     * @param userId 用户列表
     * @return 菜单权限的并集
     */
    @Override
    public List<AdminMenu> queryProjectMenuList(Long userId, Long projectId) {

        return getBaseMapper().queryProjectMenuList(userId, projectId);

    }

    /**
     * 查询项目管理用户所拥有的菜单权限
     *
     * @param userId 用户列表
     * @return 菜单权限的并集
     */
    @Override
    public List<AdminMenu> queryProjectUserMenuList(Long userId) {

        return getBaseMapper().queryProjectUserMenuList(userId);

    }

    @Override
    public List<AdminMenu> queryMenuListByRoleIds(List<Long> roleIds) {
        return getBaseMapper().queryMenuListByRoleIds(roleIds);
    }

    @Override
    public Integer queryHasMenuAuthByByRoleIds(List<Long> roleIds, Long menuId) {
        return getBaseMapper().queryHasMenuAuthByByRoleIds(roleIds, menuId);
    }

    /**
     * 查询公海菜单权限
     *
     * @param userId 用户ID
     * @param deptId 部门ID
     * @return data
     */
    @Override
    public Map<String, Long> queryPoolReadAuth(Long userId, Long deptId, List<Long> deptIds) {
        return getBaseMapper().queryPoolReadAuth(userId, deptId, deptIds);
    }


    private static final String HRM = "hrm";

    private static final String FINANCE = "finance";

    private static final String SCRM = "scrm";

    /**
     * 根据类型查询菜单
     *
     * @param typeEnum type
     * @return data
     */
    @Override
    public JSONObject getMenuListByType(AdminRoleTypeEnum typeEnum) {
        JSONObject object = new JSONObject();
        String realm = typeEnum.getName();
        switch (typeEnum) {
            case CUSTOMER_MANAGER: {
                AdminMenuVO bi = queryMenuListByRealm("bi");
                List<AdminMenuVO> biList = getMenuList(bi.getMenuId(), "oa", "jxc");
                bi.setChildMenu(biList);
                Map<String, String> keyMap = new HashMap<>();
                keyMap.put("menuName_resourceKey", "promission.system." + bi.getMenuId());
                bi.setLanguageKeyMap(keyMap);
                object.put("bi", bi);
                break;
            }
            case OA: {
                AdminMenuVO bi = queryMenuListByRealm("bi");
                String[] realmArr = new String[]{"achievement", "business", "customer", "contract", "product", "portrait", "ranking", "call", "jxc"};
                List<AdminMenuVO> biList = getMenuList(bi.getMenuId(), realmArr);
                bi.setChildMenu(biList);
                Map<String, String> keyMap = new HashMap<>();
                keyMap.put("menuName_resourceKey", "promission.system." + bi.getMenuId());
                bi.setLanguageKeyMap(keyMap);
                object.put("bi", bi);
                break;
            }
            case JXC:
                AdminMenuVO bi = queryMenuListByRealm("bi");
                String[] realmArr = new String[]{"achievement", "business", "customer", "contract", "product", "portrait", "ranking", "call", "oa"};
                List<AdminMenuVO> biList = getMenuList(bi.getMenuId(), realmArr);
                bi.setChildMenu(biList);
                Map<String, String> keyMap = new HashMap<>();
                keyMap.put("menuName_resourceKey", "promission.system." + bi.getMenuId());
                bi.setLanguageKeyMap(keyMap);
                object.put("bi", bi);
                break;
            default:
                break;
        }
        AdminMenuVO data = queryMenuListByRealm(realm);
        List<AdminMenuVO> menuList = getMenuList(data.getMenuId());
        if (realm.equals(AdminRoleTypeEnum.HRM.getName())) {
            //隐藏绩效
            menuList.removeIf(adminMenuVO -> "appraisal".equals(adminMenuVO.getRealm()));
        }
        if (realm.equals(AdminRoleTypeEnum.MANAGER.getName())) {
            //过滤是否购买了人资和财务系统
            List<AdminConfig> adminConfigs = ApplicationContextHolder.getBean(IAdminConfigService.class).queryConfigListByName("hrm", "finance", "scrm");
            Map<String, List<AdminConfig>> adminMap = adminConfigs.stream().collect(Collectors.groupingBy(AdminConfig::getName));
            if (!adminMap.containsKey(HRM) || adminMap.get(HRM).get(0).getStatus() == 0) {
                menuList.removeIf(adminMenuVO -> "hrm".equals(adminMenuVO.getRealm()));
            } else {
                menuList.forEach(adminMenu -> {
                    if (HRM.equals(adminMenu.getRealm())) {
                        //隐藏绩效设置
                        adminMenu.getChildMenu().removeIf(adminMenuVO -> "appraisal".equals(adminMenuVO.getRealm()));
                    }
                });
            }
            if (!adminMap.containsKey(FINANCE) || adminMap.get(FINANCE).get(0).getStatus() == 0) {
                menuList.removeIf(adminMenuVO -> "finance".equals(adminMenuVO.getRealm()));
            }
            if (!adminMap.containsKey(SCRM) || adminMap.get(SCRM).get(0).getStatus() == 0) {
                menuList.removeIf(adminMenuVO -> "scrm".equals(adminMenuVO.getRealm()));
            }
        }
        //升级删除项目和进销存  目前在代码中处理防止需求变更
//        menuList.removeIf(adminMenuVO -> "work".equals(adminMenuVO.getRealm()));
        data.setChildMenu(menuList);
        Map<String, String> keyMap = new HashMap<>();
        keyMap.put("menuName_resourceKey", "promission.system." + data.getMenuId());
        data.setLanguageKeyMap(keyMap);
        object.put("data", data);
        return object;
    }

    /**
     * 通过parentId和realm查询菜单
     *
     * @return 菜单列表
     * @author zhangzhiwei
     */
    private AdminMenuVO queryMenuListByRealm(String realm) {
        AdminMenu adminMenu = lambdaQuery().eq(AdminMenu::getParentId, 0).eq(AdminMenu::getRealm, realm).one();
        return BeanUtil.copyProperties(adminMenu, AdminMenuVO.class);
    }

    /**
     * 查询所有菜单
     *
     * @return 菜单列表
     * @author zhangzhiwei
     */
    @Override
    public List<AdminMenu> queryAllMenuList() {
        return query().list();
    }

    private List<AdminMenuVO> getMenuList(Long parentId, String... notRealm) {
        LambdaQueryChainWrapper<AdminMenu> chainWrapper = lambdaQuery();
        if (notRealm.length > 0) {
            chainWrapper.notIn(AdminMenu::getRealm, Arrays.asList(notRealm));
        }
        chainWrapper.orderByAsc(AdminMenu::getSort);
        List<AdminMenu> list = chainWrapper.list();
        if (CollectionUtil.isNotEmpty(list)) {
            for (AdminMenu adminMenu : list) {
                Map<String, String> keyMap = new HashMap<>();
                keyMap.put("menuName_resourceKey", "promission.system." + adminMenu.getMenuId());
                adminMenu.setLanguageKeyMap(keyMap);
            }
        }
        return RecursionUtil.getChildListTree(list, "parentId", parentId, "menuId", "childMenu", AdminMenuVO.class);
    }

    @Override
    public Long queryMenuId(String realm1, String realm2, String realm3) {
        return getBaseMapper().queryMenuId(realm1, realm2, realm3);
    }


    @Override
    public List<AdminMenu> queryMenuListByProjectType(Integer projectType) {
        return getBaseMapper().queryMenuListByProjectType(projectType);
    }
}
